//
//  LBBoxBlurFilter.mm
//  OpenGLGame
//
//  Created by Nguyen Cong Huy on 11/27/12.
//  Copyright (c) 2012 UIT. All rights reserved.
//

#include <iostream>
#include "LBBoxBlurFilter.h"
#include "LBGraphics.h"

char boxBlurVerShaderStr[] = ""

"attribute vec4 position;"
"attribute vec2 texCoor;"

"uniform mat4 mWorld;"
"uniform mat4 mProjection;"

"uniform float texelWidthOffset; "
"uniform float texelHeightOffset; "

"uniform highp float blurSize;"

"varying vec2 centerTextureCoordinate;"
"varying vec2 oneStepLeftTextureCoordinate;"
"varying vec2 twoStepsLeftTextureCoordinate;"
"varying vec2 oneStepRightTextureCoordinate;"
"varying vec2 twoStepsRightTextureCoordinate;"

"void main()"
"{"
"    gl_Position = mProjection * mWorld * position;"

"    vec2 firstOffset = vec2(1.5 * texelWidthOffset, 1.5 * texelHeightOffset) * blurSize;"
"    vec2 secondOffset = vec2(3.5 * texelWidthOffset, 3.5 * texelHeightOffset) * blurSize;"

"    centerTextureCoordinate = texCoor;"
"    oneStepLeftTextureCoordinate = texCoor - firstOffset;"
"    twoStepsLeftTextureCoordinate = texCoor - secondOffset;"
"    oneStepRightTextureCoordinate = texCoor + firstOffset;"
"    twoStepsRightTextureCoordinate = texCoor + secondOffset;"
"}";

char boxBlurFragShaderStr[] = ""
"precision highp float;"

"uniform sampler2D texture;"

"varying vec2 centerTextureCoordinate;"
"varying vec2 oneStepLeftTextureCoordinate;"
"varying vec2 twoStepsLeftTextureCoordinate;"
"varying vec2 oneStepRightTextureCoordinate;"
"varying vec2 twoStepsRightTextureCoordinate;"

"void main()"
"{"
"    lowp vec4 fragmentColor = texture2D(texture, centerTextureCoordinate) * 0.2;"
"    fragmentColor += texture2D(texture, oneStepLeftTextureCoordinate) * 0.2;"
"    fragmentColor += texture2D(texture, oneStepRightTextureCoordinate) * 0.2;"
"    fragmentColor += texture2D(texture, twoStepsLeftTextureCoordinate) * 0.2;"
"    fragmentColor += texture2D(texture, twoStepsRightTextureCoordinate) * 0.2;"



"    gl_FragColor = fragmentColor;"
"}";


LBBoxBlurFilter::LBBoxBlurFilter(){
    init(boxBlurVerShaderStr, boxBlurFragShaderStr, boxBlurVerShaderStr, boxBlurFragShaderStr);
    LBGraphics::getInstance()->useProgram(program);
    blurSizeUniform = program->uniformIndex("blurSize");
    LBGraphics::getInstance()->useProgram(program2);
    blurSizeUniform2 = program2->uniformIndex("blurSize");
    
    setBlurSize(1.0);
}

void LBBoxBlurFilter::setBlurSize(float blurSize){
    this->blurSize = blurSize;
    LBGraphics::getInstance()->useProgram(program);
    glUniform1f(blurSizeUniform, blurSize);
    LBGraphics::getInstance()->useProgram(program2);
    glUniform1f(blurSizeUniform2, blurSize);
}